#ifndef CLIB_CLIB_CONTAINER_STACK_H
#define CLIB_CLIB_CONTAINER_STACK_H

#include "../../base/clib_base.h"

CLIB_CPLUS_SUPPORT_START

/**
 * 栈对象
 */
struct clib_container_stack;

/**
 * 栈配置对象
 */
struct clib_container_stack_conf {
    /**
     * 内存分配函数
     * @param size 需要分配的大小
     * @return
     */
    void *(*mem_malloc_func)(size_t size);

    /**
     * 内存释放函数
     * @param block 块指针
     */
    void (*mem_free_func)(void *block);

    /**
     * 内存拷贝函数
     * @param target 目标
     * @param src 源
     * @param size 大小
     * @return
     */
    void *(*mem_copy_func)(void *target, const void *src, size_t size);
};

/**
 * 创建一个栈
 * @param conf 配置文件
 * @param out 创建好的栈
 * @return
 * 成功 0
 * 失败 非0
 */
int clib_container_stack_create_with_conf(
        struct clib_container_stack_conf *conf,
        struct clib_container_stack **out);


/**
 * 销毁一个栈
 * @param stack 栈对象
 */
void clib_container_stack_destroy(
        struct clib_container_stack *stack);


/**
 * 压栈
 * @param stack 栈对象
 * @param element 压栈元素
 * @return
 * 成功 0
 * 失败 非0
 */
int clib_container_stack_push(
        struct clib_container_stack *stack,
        void *element);

/**
 * 返回栈顶元素
 * @param stack 栈对象
 * @param out 存储压顶元素
 * @return
 * 成功 0
 * 失败 非0
 */
int clib_container_stack_peek(
        struct clib_container_stack *stack,
        void **out);


/**
 * 弹栈
 * @param stack 栈对象
 * @param out 存储栈顶元素
 * @return
 * 成功 0
 * 失败 非0
 */
int clib_container_stack_pop(
        struct clib_container_stack *stack,
        void **out);


/**
 * 获取当前元素个数
 * @param stack 栈对象
 * @return 当前元素个数
 *
 */
size_t clib_container_stack_get_current_size(
        struct clib_container_stack *stack);


CLIB_CPLUS_SUPPORT_END

#endif //CLIB_CLIB_CONTAINER_STACK_H
